package com.jzo2o.customer.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.jzo2o.common.model.CurrentUserInfo;
import com.jzo2o.common.model.PageResult;
import com.jzo2o.customer.enums.CertificationStatusEnum;
import com.jzo2o.customer.mapper.WorkerCertificationAuditMapper;
import com.jzo2o.customer.model.domain.WorkerCertification;
import com.jzo2o.customer.model.domain.WorkerCertificationAudit;
import com.jzo2o.customer.model.dto.WorkerCertificationUpdateDTO;
import com.jzo2o.customer.model.dto.request.CertificationAuditReqDTO;
import com.jzo2o.customer.model.dto.request.WorkerCertificationAuditAddReqDTO;
import com.jzo2o.customer.model.dto.request.WorkerCertificationAuditPageQueryReqDTO;
import com.jzo2o.customer.model.dto.response.RejectReasonResDTO;
import com.jzo2o.customer.model.dto.response.WorkerCertificationAuditResDTO;
import com.jzo2o.customer.service.IServeProviderService;
import com.jzo2o.customer.service.IWorkerCertificationAuditService;
import com.jzo2o.customer.service.IWorkerCertificationService;
import com.jzo2o.mvc.utils.UserContext;
import com.jzo2o.mysql.utils.PageUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.time.LocalDateTime;

/**
 * @Author: wen
 * @Time: 2024-04-26 11:11
 * @Version: 1.0
 */
@Service
public class WorkerCertificationAuditServiceImpl extends ServiceImpl<WorkerCertificationAuditMapper, WorkerCertificationAudit> implements IWorkerCertificationAuditService {

    @Resource
    private IWorkerCertificationService workerCertificationService;

    @Resource
    private IServeProviderService serveProviderService;


    /**
     * 服务人员申请资质认证
     *
     * @param workerCertificationAuditAddReqDTO 认证申请请求体
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void applyCertification(WorkerCertificationAuditAddReqDTO workerCertificationAuditAddReqDTO) {
        //1.新增申请资质认证记录
        WorkerCertificationAudit workerCertificationAudit = BeanUtil.toBean(workerCertificationAuditAddReqDTO, WorkerCertificationAudit.class);
        //默认未审核
        workerCertificationAudit.setAuditStatus(0);
        baseMapper.insert(workerCertificationAudit);
        //查询认证记录
        Long serveProviderId = workerCertificationAuditAddReqDTO.getServeProviderId();
        WorkerCertification workerCertification = workerCertificationService.getById(serveProviderId);
        if (ObjectUtil.isNotNull(workerCertification)) {
            //2.将认证信息状态更新为认证中
            workerCertification.setCertificationStatus(CertificationStatusEnum.PROGRESSING.getStatus());
            workerCertificationService.updateById(workerCertification);
        } else {
            workerCertification = new WorkerCertification();
            workerCertification.setId(serveProviderId);
            workerCertification.setCertificationStatus(CertificationStatusEnum.PROGRESSING.getStatus());
            workerCertificationService.save(workerCertification);
        }
    }


    /**
     * 查询最新的驳回原因
     * 本方法不需要参数，它通过查询数据库来获取当前用户最近一次被驳回的原因。
     * 查询条件基于当前用户的ID，查询结果按创建时间降序排列，并仅返回第一个结果（即最新的记录）。
     * @return RejectReasonResDTO 包含最新的驳回原因的数据传输对象。
     */
    @Override
    public RejectReasonResDTO queryCurrentUserLastRejectReason() {
        LambdaQueryWrapper<WorkerCertificationAudit> queryWrapper = Wrappers.<WorkerCertificationAudit>lambdaQuery()
                .eq(WorkerCertificationAudit::getServeProviderId, UserContext.currentUserId())
                .orderByDesc(WorkerCertificationAudit::getCreateTime)
                .last("limit 1");
        WorkerCertificationAudit workerCertificationAudit = baseMapper.selectOne(queryWrapper);
        return new RejectReasonResDTO(workerCertificationAudit.getRejectReason());
    }


    /**
     * 分页查询
     *
     * @param dto 分页查询条件
     * @return 分页结果
     */
    @Override
    public PageResult<WorkerCertificationAuditResDTO> pageQuery(WorkerCertificationAuditPageQueryReqDTO dto) {
        Page<WorkerCertificationAudit> page = PageUtils.parsePageQuery(dto, WorkerCertificationAudit.class);
        LambdaQueryWrapper<WorkerCertificationAudit> queryWrapper = Wrappers.<WorkerCertificationAudit>lambdaQuery()
                .like(ObjectUtil.isNotEmpty(dto.getName()), WorkerCertificationAudit::getName, dto.getName())
                .eq(ObjectUtil.isNotEmpty(dto.getIdCardNo()), WorkerCertificationAudit::getIdCardNo, dto.getIdCardNo())
                .eq(ObjectUtil.isNotEmpty(dto.getAuditStatus()), WorkerCertificationAudit::getAuditStatus, dto.getAuditStatus())
                .eq(ObjectUtil.isNotEmpty(dto.getCertificationStatus()), WorkerCertificationAudit::getCertificationStatus, dto.getCertificationStatus());
        Page<WorkerCertificationAudit> result = baseMapper.selectPage(page, queryWrapper);
        return PageUtils.toPage(result, WorkerCertificationAuditResDTO.class);
    }


    /**
     * 认证审核
     *
     * @param id
     * @param dto
     */
    @Override
    public void auditCertification(Long id, CertificationAuditReqDTO dto) {
        // 获取当前审核人的信息
        CurrentUserInfo userInfo = UserContext.currentUser();

        LambdaUpdateWrapper<WorkerCertificationAudit> wrapper =
                Wrappers.<WorkerCertificationAudit>lambdaUpdate()
                        // 比对ID
                        .eq(WorkerCertificationAudit::getId, id)
                        // 设置审核人的ID
                        .set(WorkerCertificationAudit::getAuditorId, userInfo.getId())
                        // 设置审核人的姓名
                        .set(WorkerCertificationAudit::getAuditorName, userInfo.getName())
                        // 设置审核状态
                        .set(WorkerCertificationAudit::getAuditStatus, 1)
                        // 设置审核的时间
                        .set(WorkerCertificationAudit::getAuditTime, LocalDateTime.now())
                        // 设置认证的状态
                        .set(WorkerCertificationAudit::getCertificationStatus, dto.getCertificationStatus())
                        // 添加驳回的原因
                        .set(ObjectUtil.isNotEmpty(dto.getRejectReason()), WorkerCertificationAudit::getRejectReason, dto.getRejectReason());
        // 设置好了就进行更新
        super.update(wrapper);

        // 根据ID获取认证审核信息，为后续更新准备数据
        WorkerCertificationAudit audit = baseMapper.selectById(id);
        WorkerCertificationUpdateDTO updateDTO = new WorkerCertificationUpdateDTO();
        // 设置要更新的服务提供者ID
        updateDTO.setId(audit.getServeProviderId());
        // 设置认证状态
        updateDTO.setCertificationStatus(dto.getCertificationStatus());

        // 当认证状态为成功时，执行额外的更新操作
        if (dto.getCertificationStatus().equals(CertificationStatusEnum.SUCCESS.getStatus())) {
            // 更新服务人员/机构的名称
            serveProviderService.updateNameById(audit.getServeProviderId(), audit.getName());

            // 组装更新所需的所有信息
            updateDTO.setName(audit.getName());
            updateDTO.setIdCardNo(audit.getIdCardNo());
            updateDTO.setFrontImg(audit.getFrontImg());
            updateDTO.setBackImg(audit.getBackImg());
            updateDTO.setCertificationMaterial(audit.getCertificationMaterial());
            updateDTO.setCertificationTime(audit.getAuditTime());
        }
        // 根据更新DTO更新服务提供者的认证信息
        workerCertificationService.updateById(updateDTO);
    }

}
